package com.gitee.feizns.webtemplate.entity.ao.commons.page;

import com.gitee.feizns.webtemplate.commons.data.order.Order;
import com.gitee.feizns.webtemplate.commons.data.order.OrderColumn;
import com.gitee.feizns.webtemplate.commons.data.page.OrderPagination;
import com.gitee.feizns.webtemplate.commons.data.page.OrderRowBounds;
import lombok.Data;
import lombok.EqualsAndHashCode;
import org.apache.ibatis.session.RowBounds;

import java.util.Arrays;
import java.util.List;

/**
 * 分页筛选
 * @author feizns
 * @since 2019/5/10
 */
@Data
@EqualsAndHashCode(callSuper = false)
public class PageFilter {

    /**
     * 页数：默认第一页
     */
    private int page_no = 1;

    /**
     * 页大小
     */
    private Integer per_page;

    /**
     * 起始偏移量
     */
    private int offset = RowBounds.NO_ROW_OFFSET;

    /**
     * 最大数量
     */
    private int limit = RowBounds.NO_ROW_LIMIT;

    /**
     * 排序：默认升序
     */
    private Order order = Order.asc;

    /**
     * 排序字段
     */
    private String order_by;

    /**
     * 排序字段列表
     */
    private List<OrderByColumn> order_by_columns;

    /**
     * 转换当前对象为 rowBounds
     * 如果有 page 则 page 优先
     * 没有则 使用 offset 和 limit
     * @return
     */
    public RowBounds toRowBounds() {
        OrderColumn[] orderBy = getOrderBy();

        return per_page != null
                ? createOrderPagination(orderBy)
                : createOrderRowBounds(orderBy);
    }

    private OrderPagination createOrderPagination(OrderColumn... orderBy) {
        return orderBy != null
                ? new OrderPagination(page_no, per_page, orderBy)
                : new OrderPagination(page_no, per_page);
    }

    private RowBounds createOrderRowBounds(OrderColumn... orderBy) {
        if ( orderBy == null ) {
            if ( limit == RowBounds.NO_ROW_LIMIT
                    && offset == RowBounds.NO_ROW_OFFSET )
                return RowBounds.DEFAULT;
            return new OrderRowBounds(offset, limit);
        }
        return new OrderRowBounds(offset, limit, orderBy);
    }

    /**
     * 获取排序列表
     * @return
     */
    private OrderColumn[] getOrderBy() {

        if ( order_by != null ) {
            String[] columns = order_by.split(",");
            return Arrays.stream(columns)
                    .map(this::strMapOrderColumn)
                    .toArray(OrderColumn[]::new);
        }

        if ( order_by_columns != null ) {
            return order_by_columns.stream()
                    .map(this::mapOrderColumn)
                    .toArray(OrderColumn[]::new);
        }

        return null;
    }

    private OrderColumn strMapOrderColumn(String columns) {
        return new OrderColumn(columns, order);
    }

    private OrderColumn mapOrderColumn(OrderByColumn columns) {
        Order order = columns.getOrder();
        return new OrderColumn(columns.getName(), order == null ? Order.asc : order);
    }

    //检查合理赋值.
    public void setLimit(Integer limit) {
        if ( limit != null && limit > -1 )
            this.limit = limit;
    }

    public void setOffset(Integer offset) {
        if ( offset != null && offset > -1 )
            this.offset = offset;
    }

    public void setPage_no(Integer page_no) {
        if ( page_no != null && page_no > 0 )
            this.page_no = page_no;
    }

    public void setPer_page(Integer per_page) {
        if ( per_page != null && per_page > 0 )
            this.per_page = per_page;
    }

    public void setOrder(Order order) {
        if ( order != null )
            this.order = order;
    }

}
